home *** CD-ROM | disk | FTP | other *** search
/ Nebula 2 / Nebula Two.iso / SourceCode / Palettes / ScrollViewDeluxe / Ruler.m < prev    next >
Text File  |  1993-11-01  |  7KB  |  278 lines

  1. #import "Ruler.h"
  2.  
  3. /*
  4.  * This Ruler should really look at the NXMeasurementUnit default
  5.  * and, based on that, use the proper units (whether centimeters
  6.  * or inches) rather than just always using inches.
  7.  */
  8.  
  9. #define LINE_X (15.0)
  10. #define WHOLE_HT (10.0)
  11. #define HALF_HT (8.0)
  12. #define QUARTER_HT (4.0)
  13. #define EIGHTH_HT (2.0)
  14. #define NUM_X (3.0)
  15.  
  16. #define WHOLE (72)
  17. #define HALF (WHOLE/2)
  18. #define QUARTER (WHOLE/4)
  19. #define EIGHTH (WHOLE/8)
  20.  
  21. @implementation Ruler
  22.  
  23. + (NXCoord)width
  24. {
  25.     return 23.0;
  26. }
  27.  
  28. - initFrame:(const NXRect *)frameRect
  29. {
  30.     [super initFrame:frameRect];
  31.     [self setFont:[Font systemFontOfSize:8.0 matrix:NX_IDENTITYMATRIX]];
  32.     startX = 0;
  33.     return self;
  34. }
  35.  
  36. - setFlipped:(BOOL)flag
  37. /*
  38.  * This view doesn't work when it's "flipped," so we
  39.  * recycle that idea to mean whether the ruler has "0" at
  40.  * the origin of the view or not.
  41.  */
  42. {
  43.     flipped = flag ? YES : NO;
  44.     return self;
  45. }
  46.  
  47. - setFont:(Font *)aFont
  48. {
  49.     NXCoord as, lh;
  50.  
  51.     font = aFont;
  52.     NXTextFontInfo(aFont, &as, &descender, &lh);
  53.     if (descender < 0.0) descender = -1.0 * descender;
  54.  
  55.     return self;
  56. }
  57.  
  58. - drawHorizontal:(const NXRect *)rects
  59. {
  60.     NXRect line, clip;
  61.     int curPos, last, mod, i, j;
  62.  
  63.     PSsetgray(NX_LTGRAY);
  64.     NXRectFill(rects);
  65.  
  66.     if (lastlp >= rects->origin.x && lastlp < rects->origin.x + rects->size.width) lastlp = -1.0;
  67.     if (lasthp >= rects->origin.x && lasthp < rects->origin.x + rects->size.width) lasthp = -1.0;
  68.  
  69.     line = bounds;                /* draw bottom line */
  70.     line.size.height = 1.0;
  71.     PSsetgray(NX_DKGRAY);
  72.     if (NXIntersectionRect(rects, &line)) NXRectFill(&line);
  73.  
  74.     line = bounds;
  75.     line.size.width = 1.0;
  76.     line.origin.x = startX - 1.0;
  77.     if (NXIntersectionRect(rects, &line)) NXRectFill(&line);
  78.  
  79.     line = bounds;                /* draw ruler line */
  80.     line.origin.y = LINE_X;
  81.     line.size.height = 1.0;
  82.     line.origin.x = startX;
  83.     line.size.width = bounds.size.width - startX;
  84.  
  85.     PSsetgray(NX_BLACK);
  86.     if (NXIntersectionRect(rects, &line)) NXRectFill(&line);
  87.  
  88.     clip = *rects;
  89.     clip.origin.x = startX;
  90.     clip.size.width = bounds.size.width - startX;
  91.     if (NXIntersectionRect(rects, &clip)) {
  92.     curPos = (int)(NX_X(&clip) - startX);
  93.     last = (int)(NX_MAXX(&clip) - startX);
  94.     if (mod = (curPos % EIGHTH)) curPos -= mod;
  95.     if (mod = (last % EIGHTH)) last -= mod;
  96.     line.size.width = 1.0;
  97.     [font set];
  98.     for (j = curPos; j <= last; j += EIGHTH) {
  99.         i = flipped ? bounds.size.width - j : j;
  100.         line.origin.x =  startX + (float)i - (flipped ? 1.0 : 0.0);
  101.         if (!(i % WHOLE)) {
  102.         char buf[10];
  103.         line.origin.y = LINE_X - WHOLE_HT;
  104.         line.size.height = WHOLE_HT;
  105.         NXRectFill(&line);
  106.         PSmoveto(((float) j + NUM_X) + startX, descender + line.origin.y - 2.0);
  107.         sprintf(buf, "%d", i / WHOLE);
  108.         PSshow(buf);
  109.         } else if (!(i % HALF)) {
  110.         line.origin.y = LINE_X - HALF_HT;
  111.         line.size.height = HALF_HT;
  112.         NXRectFill(&line);
  113.         } else if (!(i % QUARTER)) {
  114.         line.origin.y = LINE_X - QUARTER_HT;
  115.         line.size.height = QUARTER_HT;
  116.         NXRectFill(&line);
  117.         } else if (!(i % EIGHTH)) {
  118.         line.origin.y = LINE_X - EIGHTH_HT;
  119.         line.size.height = EIGHTH_HT;
  120.         NXRectFill(&line);
  121.         }
  122.     }
  123.     }
  124.  
  125.     return self;
  126. }
  127.  
  128.  
  129. - drawVertical:(const NXRect *)rects
  130. {
  131.     NXRect line, clip;
  132.     int curPos, last, mod, i, j;
  133.  
  134.     PSsetgray(NX_LTGRAY);
  135.     NXRectFill(rects);
  136.  
  137.     if (lastlp >= rects->origin.y && lastlp < rects->origin.y + rects->size.height) lastlp = -1.0;
  138.     if (lasthp >= rects->origin.y && lasthp < rects->origin.y + rects->size.height) lasthp = -1.0;
  139.  
  140.     line = bounds;                /* draw bottom line */
  141.     line.origin.x = bounds.size.width - 1.0;
  142.     line.size.width = 1.0;
  143.     PSsetgray(NX_DKGRAY);
  144.     if (NXIntersectionRect(rects, &line)) NXRectFill(&line);
  145.  
  146.     line = bounds;                /* draw ruler line */
  147.     line.origin.x = bounds.size.width - LINE_X - 2.0;
  148.     line.size.width = 1.0;
  149.     PSsetgray(NX_BLACK);
  150.     if (NXIntersectionRect(rects, &line)) NXRectFill(&line);
  151.  
  152.     clip = *rects;
  153.     line.origin.x++;
  154.     if (NXIntersectionRect(rects, &clip)) {
  155.     curPos = (int)(NX_Y(&clip));
  156.     last = (int)(NX_MAXY(&clip));
  157.     if (flipped) {
  158.         if (mod = ((int)(bounds.size.height - curPos) % EIGHTH)) curPos += mod;
  159.         if (mod = ((int)(bounds.size.height - last) % EIGHTH)) last += mod;
  160.     } else {
  161.         if (mod = (curPos % EIGHTH)) curPos -= mod;
  162.         if (mod = (last % EIGHTH)) last -= mod;
  163.     }
  164.     line.size.height = 1.0;
  165.     [font set];
  166.     for (j = curPos; j <= last; j += EIGHTH) {
  167.         i = flipped ? bounds.size.height - j : j;
  168.         line.origin.y = (float)j - (flipped ? 1.0 : 0.0);
  169.         if (!(i % WHOLE)) {
  170.         char buf[10];
  171.         line.size.width = WHOLE_HT;
  172.         NXRectFill(&line);
  173.         PSmoveto(line.origin.x + 5.0, (float)j + (flipped ? - 10.0 : 2.0));
  174.         sprintf(buf, "%d", i / WHOLE);
  175.         PSshow(buf);
  176.         } else if (!(i % HALF)) {
  177.         line.size.width = HALF_HT;
  178.         NXRectFill(&line);
  179.         } else if (!(i % QUARTER)) {
  180.         line.size.width = QUARTER_HT;
  181.         NXRectFill(&line);
  182.         } else if (!(i % EIGHTH)) {
  183.         line.size.width = EIGHTH_HT;
  184.         NXRectFill(&line);
  185.         }
  186.     }
  187.     }
  188.  
  189.     return self;
  190. }
  191.  
  192. - drawSelf:(const NXRect *) rects :(int)rectCount
  193. {
  194.     if (frame.size.width < frame.size.height) {
  195.     [self drawVertical:rects];
  196.     } else {
  197.     [self drawHorizontal:rects];
  198.     }
  199.     return self;
  200. }
  201.  
  202.  
  203. #define SETPOSITION(value) (isVertical ? (rect.origin.y = value - (absolute ? 0.0 : 1.0)) : (rect.origin.x = value + (absolute ? 0.0 : startX)))
  204. #define SETSIZE(value) (isVertical ? (rect.size.height = value) : (rect.size.width = value))
  205. #define SIZE (isVertical ? rect.size.height : rect.size.width)
  206.  
  207. - doShowPosition:(NXCoord)lp :(NXCoord)hp absolute:(BOOL)absolute
  208. {
  209.     NXRect rect;
  210.     BOOL isVertical = (frame.size.width < frame.size.height);
  211.  
  212.     rect = bounds;
  213.  
  214.     if (!absolute && !isVertical) {
  215.     if (lp < 0.0) lp -= startX;
  216.     if (hp < 0.0) hp -= startX;
  217.     }
  218.  
  219.     SETSIZE(1.0);
  220.     lastlp = SETPOSITION(lp);
  221.     NXHighlightRect(&rect);
  222.     lasthp = SETPOSITION(hp);
  223.     NXHighlightRect(&rect);
  224.  
  225.     return self;
  226. }
  227.  
  228. - showPosition:(NXCoord)lp :(NXCoord)hp
  229. {
  230.     [self lockFocus];
  231.     if (notHidden) [self doShowPosition:lastlp :lasthp absolute:YES];
  232.     [self doShowPosition:lp :hp absolute:NO];
  233.     [self unlockFocus];
  234.     notHidden = YES;
  235.     return self;
  236. }
  237.  
  238. - hidePosition
  239. {
  240.     if (notHidden) {
  241.     [self lockFocus];
  242.     [self doShowPosition:lastlp :lasthp absolute:YES];
  243.     [self unlockFocus];
  244.     notHidden = NO;
  245.     }
  246.     return self;
  247. }
  248.  
  249. - write:(NXTypedStream *)stream
  250. {
  251.     [super write:stream];
  252.     NXWriteTypes(stream, "@fffcc",
  253.         &font,
  254.         &descender,
  255.         &startX,
  256.         &lastlp,
  257.         &lasthp,
  258.         &flipped,
  259.         ¬Hidden);
  260.     return self;
  261. }
  262.  
  263. - read:(NXTypedStream *)stream
  264. {
  265.     [super read:stream];
  266.     NXReadTypes(stream, "@fffcc",
  267.         &font,
  268.         &descender,
  269.         &startX,
  270.         &lastlp,
  271.         &lasthp,
  272.         &flipped,
  273.         ¬Hidden);
  274.     return self;
  275. }
  276.  
  277. @end
  278.